// Copyright DustedPixels.com 2008. All rights reserved.

package com.dustedpixels.jasmin.unit.ula;

import com.dustedpixels.jasmin.unit.Unit;

/**
 * Controls clock signal sent to Z80.
 * 
 * @author micapolos@gmail.com (Michal Pociecha-Los)
 */
public final class ClockControl implements Unit {
  // (input) input clock signal, 3.5 Mhz
  public boolean CLK_IN;
  
  // (input) address bus, bits 0, 14 and 15 are meaningful only
  public int ADDR;
  
  // (input) IORQ signal from Z80
  public boolean IORQ;
  
  // (input) MREQ signal from Z80
  public boolean MREQ;
  
  // (input) contention period
  public boolean CONT;
  
  // (output) output, contented clock signal 3.5Mhz, driving Z80
  public boolean CLK_OUT = false;
  
  private boolean lastClkIn = false;
  private boolean lastClkOut = false;
  private boolean waitCancel = false;
  
  public void updateEndPoints() {
    if (lastClkIn != CLK_IN) {
      if (CLK_IN) {
        boolean waitReq = ((ADDR & 0xC000) == 0x4000) || (((ADDR & 0x0001) == 0x0000) && IORQ);
        CLK_OUT = CLK_IN || (CONT && waitReq && !waitCancel);
        if (lastClkOut != CLK_OUT) {
          if (CLK_OUT) {
            waitCancel = MREQ || IORQ;
          }
          lastClkOut = CLK_OUT;
        }
      }
      lastClkIn = CLK_IN;
    }
  }
}
